package com.ctsi.uaa.service.impl;

import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.ctsi.core.common.context.MarsContextHolder;
import com.ctsi.core.common.exception.MarsException;
import com.ctsi.core.common.util.$;
import com.ctsi.core.common.util.RequestHolder;
import com.ctsi.core.security.userdetails.MarsUser;
import com.ctsi.core.security.userdetails.MarsUserDetailsService;
import com.ctsi.system.dto.UserInfo;
import com.ctsi.system.entity.User;
import com.ctsi.system.entity.ZsjUser;
import com.ctsi.system.service.IUserService;
import com.ctsi.system.service.IZsjUserService;
import com.ctsi.uaa.enums.UaaExceptionEnum;
import com.ctsi.uaa.enums.UserType;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.authority.AuthorityUtils;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import java.util.Collection;


/**
 * @version 1.0
 * @author: wang xiao xiang
 * @date: 2021/8/10 11:04
 */
@Slf4j
@Service
public class UserDetailsServiceImpl implements MarsUserDetailsService {

    public static final int ENABLE = 0;
    public static final int DISABLE = 1;

    @Autowired
    @SuppressWarnings("ALL")
    private HttpServletRequest request;

    @Resource
    private IUserService userService;

    @Resource
    private IZsjUserService zsjUserService;

    @Override
    public UserDetails loadUserByUsername(String userName) throws UsernameNotFoundException {
        User user = userService.getOne(Wrappers.<User>lambdaQuery()
                .eq(User::getAccount, userName));
        //将登录人ID设置到上下文中
        MarsContextHolder.setUserId(user.getId());
        UserInfo userInfo = userService.getUserInfo(user);
        checkUserInfo(userInfo, user.getName());
        userInfo.setType(UserType.SYSTEM.getType());
        userInfo.setUserName(userName);
        return getUserDetails(userInfo);

    }

    @Override
    public UserDetails loadUserByMobile(String mobile) throws UsernameNotFoundException {
        User user = userService.getOne(Wrappers.<User>lambdaQuery().eq(User::getTel, mobile));
        UserInfo userInfo = userService.getUserInfo(user);
        checkUserInfo(userInfo, mobile);
        userInfo.setType(UserType.MOBILE.getType());
        userInfo.setUserName(mobile);
        return getUserDetails(userInfo);
    }

    @Override
    public UserDetails loadUserBySocial(String userName) throws UsernameNotFoundException {
        ZsjUser user = zsjUserService.getOne(Wrappers.<ZsjUser>lambdaQuery()
                .eq(ZsjUser::getStaffAccount, userName));
        UserInfo userInfo = zsjUserService.getUserInfo(user);
        checkUserInfo(userInfo, userName);
        userInfo.setType(UserType.TELECOM.getType());
        userInfo.setUserName(userName);
        return getZsjUserDetails(userInfo);
    }

    @Override
    public UserDetails loadUserByAppLogin(String username) throws UsernameNotFoundException {
//        AppUser appUser = appUserProvider.getUserByUserName(username).getData();
//        Collection<? extends GrantedAuthority> authorities
//                = AuthorityUtils.commaSeparatedStringToAuthorityList("app");
//        return new MarsUser(appUser.getId(), RequestHolder.getHttpServletRequestIpAddress(request), 1, appUser.getPhone(), appUser.getAvatar(),
//                "0000", appUser.getUsername(), appUser.getPassword(), ENABLE == appUser.getStatus(),
//                true, true, true, authorities);
        return null;
    }

    private void checkUserInfo(UserInfo userInfo, String account) {
        MarsContextHolder.setUserName(account);
        if ($.isNull(userInfo)) {
            throw new MarsException(UaaExceptionEnum.FEIGN_REQUEST_ERROR);
        }
//        if ($.isEmpty(userInfo.getUser())) {
//            throw new MarsException(userInfo.getErrorMessage());
//        }
//        if (DISABLE == userInfo.getUser().getStatus()) {
//            throw new MarsException(UaaExceptionEnum.USER_DISABLE);
//        }
    }

    private UserDetails getUserDetails(UserInfo userInfo) {
        User user = userInfo.getUser();
        Collection<? extends GrantedAuthority> authorities
                = AuthorityUtils.commaSeparatedStringToAuthorityList($.join(userInfo.getRoleIds()));
        return new MarsUser(user.getId(), RequestHolder.getHttpServletRequestIpAddress(request), userInfo.getType(), user.getTel(), user.getAvatar(),
                user.getTenantId().toString(), userInfo.getUserName(), user.getPassword(), ENABLE == user.getStatus(),
                true, true, true, authorities);
    }

    private UserDetails getZsjUserDetails(UserInfo userInfo) {
        ZsjUser user = userInfo.getZsjuser();
        Collection<? extends GrantedAuthority> authorities
                = AuthorityUtils.commaSeparatedStringToAuthorityList($.join(userInfo.getRoleIds()));
        return new MarsUser(user.getStaffId(), RequestHolder.getHttpServletRequestIpAddress(request), userInfo.getType(), user.getMobilePhone(), "",
                "1", userInfo.getUserName(), "", true,
                true, true, true, authorities);
    }
}